#include <iostream>
#include <pthread.h>
#include <unistd.h>

using namespace std;

int cnt = 0;
 
//定义一把锁
pthread_mutex_t mutex  = PTHREAD_MUTEX_INITIALIZER;
//定义一个条件变量
pthread_cond_t cond  = PTHREAD_COND_INITIALIZER;

void *Count(void *args)
{
    
    pthread_detach(pthread_self()); //线程分离
    uint64_t number = (uint64_t)args;
    cout << "pthread: " << number << " create success" <<endl;

    while(true)
    {
        
        pthread_mutex_lock(&mutex);  //加锁
        //等待条件满足
        //临界资源不就绪的时候，我让线程去休眠,所以说临界资源使用状态的
        //怎么知道临界资源就不就绪，是判断出来的，所以判断就是访问临界资源，判断必须在加锁之后

        //pthread_cond_wait会帮我们释放锁
        pthread_cond_wait(&cond, &mutex);

        //不管临界资源的状态情况
        cout << "pthread: " << number <<", cnt: " << cnt++ << endl;
        
        pthread_mutex_unlock(&mutex);//解锁

    }
}

int main()
{

    for(uint64_t i = 0; i < 5; i++)
    {
        pthread_t tid;
        pthread_create(&tid,nullptr,Count, (void*)i);
        usleep(1000);  
    }
    sleep(3);
    cout << "main thread ctrl begin: " << endl;

    while(true)
    {
        sleep(1);
        //唤醒cond等待队列中等待的一个线程，默认是第一个
        pthread_cond_signal(&cond);
        cout << "signal one thread..." <<endl;
    }
    return 0;
}



// int cnt = 0;
 
// //定义一把锁
// pthread_mutex_t mutex  = PTHREAD_MUTEX_INITIALIZER;
// //定义一个条件变量
// pthread_cond_t cond  = PTHREAD_COND_INITIALIZER;

// void *Count(void *args)
// {
    
//     pthread_detach(pthread_self()); //线程分离
//     uint64_t number = (uint64_t)args;
//     cout << "pthread: " << number << "create success" <<endl;

//     while(true)
//     {
        
//         // pthread_mutex_lock(&mutex);  //加锁
//         //等待条件满足
//         // pthread_cond_wait(&cond, &mutex); 
//         //不管临界资源的状态情况
//         cout << "pthread: " << number <<", cnt: " << cnt++ << endl;
//         // pthread_mutex_unlock(&mutex);//解锁

//     }
// }

// int main()
// {

//     for(uint64_t i = 0; i < 5; i++)
//     {
//         pthread_t tid;
//         pthread_create(&tid,nullptr,Count, (void*)i);
//     }

//     while(true)
//     {
//         sleep(1);
//     }
//     return 0;
// }
